package com.cloud.code.dynaproxy.aop;

import lombok.SneakyThrows;

import java.beans.BeanInfo;
import java.beans.Introspector;
import java.beans.PropertyDescriptor;
import java.io.InputStream;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.Arrays;
import java.util.Properties;

public class BeanFactory {

    Properties properties = new Properties();

    @SneakyThrows
    public BeanFactory(InputStream inputStream) {
        properties.load(inputStream);
    }

    @SneakyThrows
    public Object getBean(String name) {
        String className = properties.getProperty("bean");

        //获取代理类
        Class<?> aClass = Class.forName(className);
        Object obj = aClass.newInstance();
        //根据配置文件获取成员属性类，并组装
        Object advice = Class.forName(properties.getProperty(name + ".advice")).newInstance();
        Object target = Class.forName(properties.getProperty(name + ".target")).newInstance();
        //利用内省获取成员变量， 并赋值
        BeanInfo beanInfo = Introspector.getBeanInfo(aClass);
        PropertyDescriptor[] propertyDescriptors = beanInfo.getPropertyDescriptors();
        Arrays.stream(propertyDescriptors).forEach(tem -> {
            Method writeMethod = tem.getWriteMethod();
            String temName = tem.getName();
            if ("advice".equalsIgnoreCase(temName)) {
                try {
                    writeMethod.invoke(obj, advice);
                } catch (IllegalAccessException e) {
                    e.printStackTrace();
                } catch (InvocationTargetException e) {
                    e.printStackTrace();
                }
            } else if ("target".equalsIgnoreCase(temName)) {
                try {
                    writeMethod.invoke(obj, target);
                } catch (IllegalAccessException e) {
                    e.printStackTrace();
                } catch (InvocationTargetException e) {
                    e.printStackTrace();
                }
            }
        });

        return obj;
    }
}
